package github.leavesczy.matisse.samples

import android.net.Uri
import android.os.Bundle
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import android.widget.AdapterView
import android.widget.ArrayAdapter
import android.widget.Button
import android.widget.CheckBox
import android.widget.RadioButton
import android.widget.RadioGroup
import android.widget.Spinner
import android.widget.TextView
import androidx.appcompat.app.AppCompatActivity
import androidx.appcompat.app.AppCompatDelegate
import androidx.core.view.WindowCompat
import androidx.core.view.WindowInsetsControllerCompat
import androidx.recyclerview.widget.GridLayoutManager
import androidx.recyclerview.widget.RecyclerView
import android.graphics.Bitmap
import android.graphics.BitmapFactory
import java.io.InputStream
import github.leavesczy.matisse.MatisseCaptureContract
import github.leavesczy.matisse.MatisseContract
import github.leavesczy.matisse.MediaResource
import github.leavesczy.matisse.MediaType
import github.leavesczy.matisse.samples.logic.MediaCaptureStrategy
import github.leavesczy.matisse.samples.logic.MediaFilterStrategy
import github.leavesczy.matisse.samples.logic.MediaImageEngine

/**
 * @Author: leavesCZY
 * @Date: 2024/2/21 12:01
 * @Desc: 传统XML布局方式的MainActivity
 */
class TraditionalMainActivity : AppCompatActivity() {

    private lateinit var gridColumnsGroup: RadioGroup
    private lateinit var maxSelectableGroup: RadioGroup
    private lateinit var fastSelectCheckBox: CheckBox
    private lateinit var singleMediaTypeCheckBox: CheckBox
    private lateinit var imageEngineSpinner: Spinner
    private lateinit var filterStrategySpinner: Spinner
    private lateinit var captureStrategySpinner: Spinner
    private lateinit var capturePreferencesCustomCheckBox: CheckBox
    private lateinit var mediaRecyclerView: RecyclerView
    private lateinit var mediaAdapter: MediaAdapter

    private var gridColumns = 4
    private var maxSelectable = 3
    private var fastSelect = false
    private var singleMediaType = false
    private var imageEngine = MediaImageEngine.Coil
    private var filterStrategy = MediaFilterStrategy.Nothing
    private var captureStrategy = MediaCaptureStrategy.Smart
    private var capturePreferencesCustom = false
    private var mediaList = mutableListOf<MediaResource>()

    private val takePictureLauncher = registerForActivityResult(
        MatisseCaptureContract()
    ) { result ->
        if (result != null) {
            mediaList.clear()
            mediaList.add(result)
            mediaAdapter.notifyDataSetChanged()
        }
    }

    private val mediaPickerLauncher = registerForActivityResult(
        MatisseContract()
    ) { result ->
        if (!result.isNullOrEmpty()) {
            mediaList.clear()
            mediaList.addAll(result)
            mediaAdapter.notifyDataSetChanged()
        }
    }

    override fun onCreate(savedInstanceState: Bundle?) {
        setSystemBarUi()
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_traditional_main)
        
        initViews()
        setupListeners()
        setupRecyclerView()
    }

    private fun setSystemBarUi() {
        WindowCompat.setDecorFitsSystemWindows(window, false)
        WindowInsetsControllerCompat(window, window.decorView).apply {
            isAppearanceLightStatusBars = false
            isAppearanceLightNavigationBars = false
        }
    }

    private fun initViews() {
        gridColumnsGroup = findViewById(R.id.gridColumnsGroup)
        maxSelectableGroup = findViewById(R.id.maxSelectableGroup)
        fastSelectCheckBox = findViewById(R.id.fastSelectCheckBox)
        singleMediaTypeCheckBox = findViewById(R.id.singleMediaTypeCheckBox)
        imageEngineSpinner = findViewById(R.id.imageEngineSpinner)
        filterStrategySpinner = findViewById(R.id.filterStrategySpinner)
        captureStrategySpinner = findViewById(R.id.captureStrategySpinner)
        capturePreferencesCustomCheckBox = findViewById(R.id.capturePreferencesCustomCheckBox)
        mediaRecyclerView = findViewById(R.id.mediaRecyclerView)

        // 设置默认选中状态
        when (gridColumns) {
            2 -> findViewById<RadioButton>(R.id.gridColumns2).isChecked = true
            3 -> findViewById<RadioButton>(R.id.gridColumns3).isChecked = true
            4 -> findViewById<RadioButton>(R.id.gridColumns4).isChecked = true
            5 -> findViewById<RadioButton>(R.id.gridColumns5).isChecked = true
        }

        when (maxSelectable) {
            1 -> findViewById<RadioButton>(R.id.maxSelectable1).isChecked = true
            2 -> findViewById<RadioButton>(R.id.maxSelectable2).isChecked = true
            3 -> findViewById<RadioButton>(R.id.maxSelectable3).isChecked = true
            4 -> findViewById<RadioButton>(R.id.maxSelectable4).isChecked = true
        }

        fastSelectCheckBox.isChecked = fastSelect
        singleMediaTypeCheckBox.isChecked = singleMediaType
        capturePreferencesCustomCheckBox.isChecked = capturePreferencesCustom
    }

    private fun setupListeners() {
        // Grid Columns
        gridColumnsGroup.setOnCheckedChangeListener { _, checkedId ->
            gridColumns = when (checkedId) {
                R.id.gridColumns2 -> 2
                R.id.gridColumns3 -> 3
                R.id.gridColumns4 -> 4
                R.id.gridColumns5 -> 5
                else -> 4
            }
        }

        // Max Selectable
        maxSelectableGroup.setOnCheckedChangeListener { _, checkedId ->
            maxSelectable = when (checkedId) {
                R.id.maxSelectable1 -> 1
                R.id.maxSelectable2 -> 2
                R.id.maxSelectable3 -> 3
                R.id.maxSelectable4 -> 4
                else -> 3
            }
        }

        // Fast Select
        fastSelectCheckBox.setOnCheckedChangeListener { _, isChecked ->
            fastSelect = isChecked
            if (isChecked) {
                maxSelectable = 1
                findViewById<RadioButton>(R.id.maxSelectable1).isChecked = true
            }
        }

        // Single Media Type
        singleMediaTypeCheckBox.setOnCheckedChangeListener { _, isChecked ->
            singleMediaType = isChecked
        }

        // Capture Preferences Custom
        capturePreferencesCustomCheckBox.setOnCheckedChangeListener { _, isChecked ->
            capturePreferencesCustom = isChecked
        }

        // Image Engine Spinner
        val imageEngineAdapter = ArrayAdapter(
            this,
            android.R.layout.simple_spinner_item,
            MediaImageEngine.entries.map { it.name }
        )
        imageEngineAdapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item)
        imageEngineSpinner.adapter = imageEngineAdapter
        imageEngineSpinner.setSelection(imageEngine.ordinal)
        imageEngineSpinner.onItemSelectedListener = object : AdapterView.OnItemSelectedListener {
            override fun onItemSelected(parent: AdapterView<*>?, view: View?, position: Int, id: Long) {
                imageEngine = MediaImageEngine.entries[position]
            }
            override fun onNothingSelected(parent: AdapterView<*>?) {}
        }

        // Filter Strategy Spinner
        val filterStrategyAdapter = ArrayAdapter(
            this,
            android.R.layout.simple_spinner_item,
            MediaFilterStrategy.entries.map { it.name }
        )
        filterStrategyAdapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item)
        filterStrategySpinner.adapter = filterStrategyAdapter
        filterStrategySpinner.setSelection(filterStrategy.ordinal)
        filterStrategySpinner.onItemSelectedListener = object : AdapterView.OnItemSelectedListener {
            override fun onItemSelected(parent: AdapterView<*>?, view: View?, position: Int, id: Long) {
                filterStrategy = MediaFilterStrategy.entries[position]
            }
            override fun onNothingSelected(parent: AdapterView<*>?) {}
        }

        // Capture Strategy Spinner
        val captureStrategyAdapter = ArrayAdapter(
            this,
            android.R.layout.simple_spinner_item,
            MediaCaptureStrategy.entries.map { it.name }
        )
        captureStrategyAdapter.setDropDownViewResource(android.R.layout.simple_spinner_dropdown_item)
        captureStrategySpinner.adapter = captureStrategyAdapter
        captureStrategySpinner.setSelection(captureStrategy.ordinal)
        captureStrategySpinner.onItemSelectedListener = object : AdapterView.OnItemSelectedListener {
            override fun onItemSelected(parent: AdapterView<*>?, view: View?, position: Int, id: Long) {
                captureStrategy = MediaCaptureStrategy.entries[position]
                capturePreferencesCustomCheckBox.isEnabled = captureStrategy != MediaCaptureStrategy.Close
            }
            override fun onNothingSelected(parent: AdapterView<*>?) {}
        }

        // Buttons
        findViewById<Button>(R.id.btnImageAndVideo).setOnClickListener {
            launchMediaPicker(MediaType.ImageAndVideo)
        }

        findViewById<Button>(R.id.btnImageOnly).setOnClickListener {
            launchMediaPicker(MediaType.ImageOnly)
        }

        findViewById<Button>(R.id.btnVideoOnly).setOnClickListener {
            launchMediaPicker(MediaType.VideoOnly)
        }

        findViewById<Button>(R.id.btnGifAndMp4).setOnClickListener {
            launchMediaPicker(MediaType.MultipleMimeType(setOf("image/gif", "video/mp4")))
        }

        findViewById<Button>(R.id.btnTakePicture).setOnClickListener {
            takePicture()
        }

        findViewById<Button>(R.id.btnSwitchTheme).setOnClickListener {
            switchTheme()
        }
    }

    private fun setupRecyclerView() {
        mediaAdapter = MediaAdapter(mediaList)
        mediaRecyclerView.layoutManager = GridLayoutManager(this, 2)
        mediaRecyclerView.adapter = mediaAdapter
    }

    private fun launchMediaPicker(mediaType: MediaType) {
        val matisse = buildMatisse(mediaType)
        mediaPickerLauncher.launch(matisse)
    }

    private fun takePicture() {
        val matisseCapture = buildMediaCaptureStrategy()
        if (matisseCapture != null) {
            takePictureLauncher.launch(matisseCapture)
        }
    }

    private fun switchTheme() {
        val currentMode = AppCompatDelegate.getDefaultNightMode()
        val newMode = if (currentMode == AppCompatDelegate.MODE_NIGHT_YES) {
            AppCompatDelegate.MODE_NIGHT_NO
        } else {
            AppCompatDelegate.MODE_NIGHT_YES
        }
        AppCompatDelegate.setDefaultNightMode(newMode)
    }

    private fun buildMatisse(mediaType: MediaType): github.leavesczy.matisse.Matisse {
        val imageEngine = when (this.imageEngine) {
            MediaImageEngine.Coil -> github.leavesczy.matisse.CoilImageEngine()
            MediaImageEngine.Glide -> github.leavesczy.matisse.GlideImageEngine()
        }

        val ignoredResourceUri: Set<Uri>
        val selectedResourceUri: Set<Uri>
        when (filterStrategy) {
            MediaFilterStrategy.Nothing -> {
                ignoredResourceUri = emptySet()
                selectedResourceUri = emptySet()
            }
            MediaFilterStrategy.IgnoreSelected -> {
                ignoredResourceUri = mediaList.map { it.uri }.toSet()
                selectedResourceUri = emptySet()
            }
            MediaFilterStrategy.AttachSelected -> {
                ignoredResourceUri = emptySet()
                selectedResourceUri = mediaList.map { it.uri }.toSet()
            }
        }

        val mediaFilter = github.leavesczy.matisse.DefaultMediaFilter(
            ignoredMimeType = emptySet(),
            ignoredResourceUri = ignoredResourceUri,
            selectedResourceUri = selectedResourceUri
        )

        return github.leavesczy.matisse.Matisse(
            gridColumns = gridColumns,
            maxSelectable = maxSelectable,
            fastSelect = fastSelect,
            mediaType = mediaType,
            mediaFilter = mediaFilter,
            imageEngine = imageEngine,
            singleMediaType = singleMediaType,
            captureStrategy = getMediaCaptureStrategy()
        )
    }

    private fun buildMediaCaptureStrategy(): github.leavesczy.matisse.MatisseCapture? {
        val captureStrategy = getMediaCaptureStrategy() ?: return null
        return github.leavesczy.matisse.MatisseCapture(captureStrategy = captureStrategy)
    }

    private fun getMediaCaptureStrategy(): github.leavesczy.matisse.CaptureStrategy? {
        val fileProviderAuthority = "github.leavesczy.matisse.samples.FileProvider"
        val captureExtra = if (capturePreferencesCustom) {
            val bundle = Bundle()
            bundle.putBoolean("android.intent.extra.USE_FRONT_CAMERA", true)
            bundle.putInt("android.intent.extras.CAMERA_FACING", 1)
            bundle
        } else {
            Bundle.EMPTY
        }

        return when (captureStrategy) {
            MediaCaptureStrategy.Smart -> {
                github.leavesczy.matisse.SmartCaptureStrategy(
                    fileProviderCaptureStrategy = github.leavesczy.matisse.FileProviderCaptureStrategy(
                        authority = fileProviderAuthority,
                        extra = captureExtra
                    )
                )
            }
            MediaCaptureStrategy.FileProvider -> {
                github.leavesczy.matisse.FileProviderCaptureStrategy(
                    authority = fileProviderAuthority,
                    extra = captureExtra
                )
            }
            MediaCaptureStrategy.MediaStore -> {
                github.leavesczy.matisse.MediaStoreCaptureStrategy(extra = captureExtra)
            }
            MediaCaptureStrategy.Close -> {
                null
            }
        }
    }

    private class MediaAdapter(private val mediaList: List<MediaResource>) : 
        RecyclerView.Adapter<MediaAdapter.MediaViewHolder>() {

        class MediaViewHolder(itemView: View) : RecyclerView.ViewHolder(itemView) {
            val imageView: android.widget.ImageView = itemView.findViewById(R.id.mediaImageView)
            val textView: TextView = itemView.findViewById(R.id.mediaTextView)
        }

        override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): MediaViewHolder {
            val view = LayoutInflater.from(parent.context)
                .inflate(R.layout.item_media, parent, false)
            return MediaViewHolder(view)
        }

        override fun onBindViewHolder(holder: MediaViewHolder, position: Int) {
            val mediaResource = mediaList[position]
            
            // 使用传统方式加载图片
            try {
                val inputStream: InputStream? = holder.itemView.context.contentResolver.openInputStream(mediaResource.uri)
                val bitmap = BitmapFactory.decodeStream(inputStream)
                holder.imageView.setImageBitmap(bitmap)
                inputStream?.close()
            } catch (e: Exception) {
                // 如果加载失败，显示默认背景
                holder.imageView.setImageResource(android.R.drawable.ic_menu_gallery)
            }

            holder.textView.text = "${mediaResource.uri}\n\n${mediaResource.path}\n\n${mediaResource.mimeType}"
        }

        override fun getItemCount(): Int = mediaList.size
    }
} 